use crate::models::{
    load_api_mapping, load_api_prefixes, load_auth, load_static_mapping, load_static_prefixes,
};
use dotenvy::dotenv;
use std::env;
use std::io::Write;
use tempfile::NamedTempFile;

// 创建一个临时的.env文件，并写入一些环境变量
fn create_dotenv_file(content: &str) -> NamedTempFile {
    let mut dotenv_file = NamedTempFile::new().unwrap();
    write!(&mut dotenv_file, "{}", content).unwrap();
    dotenv_file.flush().unwrap(); // 确保内容被写入磁盘
    dotenv_file
}

#[test]
fn test_load_static_mapping() {
    let dotenv_content = "APP_PREFIX=gate\nAPP_TARGET=http://target.com\nAPP_REPLACE=true";
    let dotenv_file = create_dotenv_file(dotenv_content);
    let dotenv_path = dotenv_file.path();

    dotenvy::from_path(dotenv_path).ok();
    let result = load_static_mapping("APP").expect("no api mappings");

    assert_eq!(result.prefix, "gate");
    assert_eq!(result.target, "http://target.com");
    assert_eq!(result.replace, true);

    // 清理测试环境
    env::remove_var("APP_PREFIX");
    env::remove_var("APP_TARGET");
    env::remove_var("APP_REPLACE");

    let _ = std::fs::remove_file(dotenv_path);
}

#[test]
fn test_load_api_mapping() {
    let dotenv_content =
        "APP_PREFIX=gate\nAPP_TARGET=http://target.com\nAPP_REPLACE=true\nAPP_NEED_CHECK_AUTH=true";
    let dotenv_file = create_dotenv_file(dotenv_content);
    let dotenv_path = dotenv_file.path();

    dotenvy::from_path(dotenv_path).ok();
    let result = load_api_mapping("APP").expect("no api mappings");

    assert_eq!(result.prefix, "gate");
    assert_eq!(result.target, "http://target.com");
    assert_eq!(result.replace, true);
    assert_eq!(result.need_check_auth, true);

    // 清理测试环境
    env::remove_var("APP_PREFIX");
    env::remove_var("APP_TARGET");
    env::remove_var("APP_REPLACE");
    env::remove_var("APP_NEED_CHECK_AUTH");

    let _ = std::fs::remove_file(dotenv_path);
}

#[test]
fn test_load_api_mapping_with_default() {
    let dotenv_content = "APP_PREFIX=gate\nAPP_TARGET=http://target.com\nAPP_REPLACE=true";
    let dotenv_file = create_dotenv_file(dotenv_content);
    let dotenv_path = dotenv_file.path();

    dotenvy::from_path(dotenv_path).ok();
    let result = load_api_mapping("APP").expect("no api mappings");

    assert_eq!(result.prefix, "gate");
    assert_eq!(result.target, "http://target.com");
    assert_eq!(result.replace, true);
    assert_eq!(result.need_check_auth, false);

    // 清理测试环境
    env::remove_var("APP_PREFIX");
    env::remove_var("APP_TARGET");
    env::remove_var("APP_REPLACE");
    env::remove_var("APP_NEED_CHECK_AUTH");

    let _ = std::fs::remove_file(dotenv_path);
}

#[test]
fn test_load_api_prefixes() {
    let dotenv_content = "API_PREFIXES=web,app";
    let dotenv_file = create_dotenv_file(dotenv_content);
    let dotenv_path = dotenv_file.path();

    dotenvy::from_path(dotenv_path).ok();
    let result = load_api_prefixes().expect("no api prefixes");

    assert_eq!(result, vec!["WEB".to_string(), "APP".to_string()]);

    // 清理测试环境
    env::remove_var("API_PREFIXES");

    let _ = std::fs::remove_file(dotenv_path);
}

#[test]
fn test_load_static_prefixes() {
    let dotenv_content = "STATIC_PREFIXES=web,app";
    let dotenv_file = create_dotenv_file(dotenv_content);
    let dotenv_path = dotenv_file.path();

    dotenvy::from_path(dotenv_path).ok();
    let result = load_static_prefixes().expect("no api prefixes");

    assert_eq!(result, vec!["WEB".to_string(), "APP".to_string()]);

    // 清理测试环境
    env::remove_var("STATIC_PREFIXES");

    let _ = std::fs::remove_file(dotenv_path);
}

#[test]
fn test_load_auth_with_valid_env() {
    let dotenv_content =
        "AUTH_REDIS_ADDR=redis_addrx\nAUTH_REDIS_PORT=333\nAUTH_URL=http://auth:8000";
    let dotenv_file = create_dotenv_file(dotenv_content);
    let dotenv_path = dotenv_file.path();

    dotenvy::from_path(dotenv_path).ok();
    let result = load_auth();

    // 断言结果是否符合预期
    let auth = &result.unwrap();
    assert_eq!(auth.redis_addr, "redis_addrx");
    assert_eq!(auth.redis_port, 333);
    assert_eq!(auth.auth_url, "http://auth:8000");

    // 清理测试环境
    env::remove_var("AUTH_REDIS_ADDR");
    env::remove_var("AUTH_REDIS_PORT");
    env::remove_var("AUTH_URL");

    let _ = std::fs::remove_file(dotenv_path);
}
#[test]
fn test_load_auth_with_missing_env() {
    // 确保环境变量没有被设置
    dotenv().ok();
    let result = load_auth();

    assert_eq!(true, result.is_none());
}

#[test]
fn test_load_auth_from_shell_env() {
    env::set_var("AUTH_REDIS_ADDR", "abc");
    env::set_var("AUTH_REDIS_PORT", "222");
    env::set_var("AUTH_URL", "bbb");

    dotenv().ok();
    let auth = load_auth().expect("none auth");

    assert_eq!(auth.redis_addr, "abc");
    assert_eq!(auth.redis_port, 222);
    assert_eq!(auth.auth_url, "bbb");

    env::remove_var("AUTH_REDIS_ADDR");
    env::remove_var("AUTH_REDIS_PORT");
    env::remove_var("AUTH_URL");
}
